/*
 * @Author: 周凯
 * @Date: 2020-10-20 14:31:24
 * @LastEditTime: 2020-10-20 15:46:06
 */
const r = [
  "HTTP/1.1 401 Unauthorized",
  'WWW-Authenticate: Digest realm="Login to f5c8557f6bee8548b0d72a1c30780e5e", qop="auth", nonce="1189347886", opaque="d6ae186150aa54aa82e816e281102905e064907f"',
  "Connection: close",
  "Set-Cookie:secure; HttpOnly",
  "CONTENT-LENGTH: 0",
  "",
  "",
];
const md5 = require("md5");
const { v4 } = require("uuid");

const data = r[1];

console.log(generateAuthorization(data, "admin", "a12345678"));
function generateAuthorization(data, username, password) {
  // 最终结果值
  const endParams = {
    realm: "",
    qop: "",
    nonce: "",
    opaque: "",
    cnonce: v4().replace(/-/gi, ""),
    nc: "00000001",
  };
  console.log("data", data);
  console.log("\n");
  const rr = data.replace("WWW-Authenticate", "Authenticate");

  rr.split(",").forEach((item) => {
    let r = item.trim().replace(/=/gi, ":");
    if (foramtParams(r, "realm:")) endParams.realm = foramtParams(r, "realm:");
    if (foramtParams(r, "qop:")) endParams.qop = foramtParams(r, "qop:");
    if (foramtParams(r, "nonce:")) endParams.nonce = foramtParams(r, "nonce:");
    if (foramtParams(r, "opaque:"))
      endParams.opaque = foramtParams(r, "opaque:");
  });
  /**
   * 获取参数时的处理
   * @param {*} data 数据
   * @param {*} val 选择搜索的值
   */
  function foramtParams(data, val) {
    if (data.indexOf(val) !== -1 || data.indexOf(val) === 0) {
      return data.substring(data.indexOf(val) + val.length).replace(/"/gi, "");
    }
    return false;
  }

  // HA1部分
  const HA1 = md5(`${username}:${endParams.realm}:${password}`);

  // HA2
  const HA2 = md5("GET:GetDeviceInfo");
  const response = md5(
    `${HA1}:${endParams.nonce}:${endParams.nc}:${endParams.cnonce}:${endParams.qop}:${HA2}`
  );
  const returnValidationHeader = `Authorization: Digest username="${username}",realm="${endParams.realm}",nonce="${endParams.nonce}",uri="GetDeviceInfo",algorithm="MD5",cnonce="${endParams.cnonce}",nc="${endParams.nc}",qop="${endParams.qop}",response="${response}"`;
  return returnValidationHeader;
}

// username----系统用户名；客户端自行填充 - admin

// realm----领域；服务端通过WWW-Authenticate头返回内容可以自己随便定，但其目的是用于提示客户端当前是什么系统，所以规范来说应类似于“myhost@testrealm.com”的形式。  -

// nonce----服务端通过WWW-Authenticate头返回的随机数 -

// uri----请求接口或资源（似乎规范来说应用GET或POST后的一样，上边例子中少了/是因为服务端没按规范实现）- GetDeviceInfo

// algorithm----后边response用的计算方法 - MD5

// cnonce----client nonce，客户端生成的随机数 - uuid

// nc----nonce count，用于标识进行请求的次数。（但你一直不变服务端也不会管你对不对）- 00000001

// qop----quality of protection，进一步限定response的计算方法，服务端通过WWW-Authenticate头返回。 -

// response----认证最主要的值，前面各字段除algorithm外全要参与该值的计算。
